package net.mysoft.framework.authority;

import java.io.IOException;
import java.lang.reflect.Method;

import javax.servlet.http.HttpServletRequest;

import net.mysoft.framework.model.Json;
import net.mysoft.framework.model.SessionInfo;
import net.mysoft.framework.util.RequestUtil;
import net.mysoft.framework.util.ResourceUtil;

import org.apache.log4j.Logger;
import org.apache.struts2.ServletActionContext;

import com.alibaba.fastjson.JSON;
import com.opensymphony.xwork2.ActionInvocation;
import com.opensymphony.xwork2.interceptor.MethodFilterInterceptor;

/**
 * 权限拦截器
 * 
 * @author liuyang
 * 
 */
public class AuthorityInterceptor extends MethodFilterInterceptor {

	private static final Logger logger = Logger.getLogger(AuthorityInterceptor.class);

	protected String doIntercept(ActionInvocation invocation) throws Exception {
		Object action = invocation.getAction(); //获得action对象   
        String methodName = invocation.getProxy().getMethod(); //通过action代理获得方法名   
        Method method = action.getClass().getMethod(methodName, null);  
        HttpServletRequest httpServletRequest = ServletActionContext.getRequest();  
 
        Command command = isPassable(httpServletRequest,method); //检查该用户是否有此方法权限   
       ////System.out.println("session:"+httpServletRequest.getSession().getAttribute(ResourceUtil.getSessionInfoName()));
        if (!command.isPassable()) {  
        	if(command.getReturnName()!=null&&"noSession".equals(command.getReturnName())){
        		return command.getReturnName();
    		}
    		Json j = new Json();
    		j.setMsg(command.getMsg());
        	//ServletActionContext.getRequest().setAttribute("msg",command.getMsg());
    		//return command.getReturnName();
    		
    		writeJson(j);
        }  
        return invocation.invoke(); 
	}

	/**
	 * 将对象转换成JSON字符串，并响应回前台
	 * 
	 * @param object
	 * @throws IOException
	 */
	public void writeJson(Object object) {
		try {
			// SerializeConfig serializeConfig = new SerializeConfig();
			// serializeConfig.setAsmEnable(false);
			// String json = JSON.toJSONString(object);
			// String json = JSON.toJSONString(object, serializeConfig, SerializerFeature.PrettyFormat);
		//	JSONObject jsonObject = JSONObject.fromObject(object); 

			String json = JSON.toJSONStringWithDateFormat(object, "yyyy-MM-dd HH:mm:ss"); 
			// String json = JSON.toJSONStringWithDateFormat(object, "yyyy-MM-dd HH:mm:ss", SerializerFeature.PrettyFormat);
			ServletActionContext.getResponse().setContentType("text/html;charset=utf-8");
			ServletActionContext.getResponse().getWriter().write(json);
			ServletActionContext.getResponse().getWriter().flush();
			ServletActionContext.getResponse().getWriter().close();
		} catch (IOException e) {
			e.printStackTrace();
		}
	}
	
	
	/**
	 * 判断被调用方法的权限许可
	 * @param httpServletRequest
	 * @param method
	 * @return
	 */
	private Command isPassable(HttpServletRequest httpServletRequest,Method method) {
		Command command = new Command();
     	String requestPath = RequestUtil.getRequestPath(httpServletRequest);
     	command.setMsg("您没有访问此功能的权限！权限路径为[" + requestPath + "]请联系管理员给你赋予相应权限。");
     	command.setReturnName("noAuthority");
     	
     	SessionInfo sessionInfo = null;
     	boolean noSession = false; //没有session
     	boolean isAdmin = false;//是否是管理员
     	boolean flag = false; //是否通过标识变量
     	
     	if(httpServletRequest.getSession()==null){
     		noSession = true;
     	}
     	if(!noSession){//如果有session
     		sessionInfo = (SessionInfo) httpServletRequest.getSession().getAttribute(ResourceUtil.getSessionInfoName());
     	}
     	if(sessionInfo!=null&&"admin".equals(sessionInfo.getLoginName())){
     		isAdmin = true;
     	}
		
		if (method != null) { //有该方法
			Permission permission = method.getAnnotation(Permission.class); // 获得该方法上的Permission注解
			String access = null;
			String name = null;
			if(permission!=null){
				access = permission.access();
			}
			if(access!=null&&access.equals(AccessType.GUEST)){//来宾权限注解+没session+没权限 也可以访问
				flag = true;
			}else if(access!=null&&access.equals(AccessType.DENY)){//除admin 都不可以访问
				if(isAdmin){
					flag = true;
				}
				flag = false;
			}else if(access!=null&&access.equals(AccessType.LOGIN)){//有session的 都可以访问
				if(sessionInfo!=null&&sessionInfo.getLoginName()!=null){
					flag = true;
				}else{
					command.setReturnName("noSession");
				}
			}else if(access!=null&&access.equals(AccessType.AUTH)){//有session有权限的可以访问
				if(sessionInfo!=null&&sessionInfo.getLoginName()!=null){//判断有session在进行权限判断
					if(isAdmin){
						flag =true;
					}else{
						flag = isPassable(httpServletRequest,sessionInfo);
					}
				}else{
					command.setReturnName("noSession");
				}	
			}else{//没有注解的方法
				if(sessionInfo!=null&&sessionInfo.getLoginName()!=null){
					flag = true;
				}else{
					command.setReturnName("noSession");
				}
			}
		}
		command.setPassable(flag);
		return command;
	}
	
	/**
	 * 从session中取用户权限判断当前调用方法是否被授权
	 * @param httpServletRequest
	 * @param sessionInfo
	 * @return
	 */
	private boolean isPassable(HttpServletRequest httpServletRequest,SessionInfo sessionInfo){
		boolean flag = false;
		if(sessionInfo!=null){
			String requestPath = RequestUtil.getRequestPath(httpServletRequest);
			String authUrls = sessionInfo.getAuthUrls();
			for (String url : authUrls.split(",")) {
				if (requestPath.equals(url)) {
					flag = true;
					break;
				}
			}
		}
		return flag;
	}
}
